#!/usr/bin/env bash
# configurable options and their default values

# example
# ./gradlew clean build -x test -DFROM_BRANCH=master \
# && quick-deploy-commerce.sh --aws-profile=NIKE.SSO.AdminRole --aws-region=cn-northwest-1 buy-o2o-simplemock ./build/libs/simplemock-1.0.0.jar

print_help="no"
aws_profile=$AWS_PROFILE
aws_region=$AWS_REGION
target=""
jar=""

# parse the cli options
for i in "$@"; do
  case $i in
    --aws-profile=*)
      aws_profile="${i#*=}"
      shift
      ;;
    --aws-region=*)
      aws_region="${i#*=}"
      shift
      ;;
    --help)
      print_help="yes"
      shift
      ;;
    *)
      if [[ "$i" = *.jar ]]; then
        jar=$i
      else
        target="$i"
      fi
      shift
      ;;
  esac
done

# assemble aws cli with options
AWS_REGION_OPTION=""
if [ -z "$aws_profile" ]; then
  echo "You don't have ther required --aws-profile parameter! Run ${bold}gimme-aws-creds${normal} first to get a valid profile!"
fi
if [ ! -z "$aws_region" ]; then
  AWS_REGION_OPTION="--region ${aws_region}"
fi
AWS_CLI_WRAPPER="aws --profile ${aws_profile} ${AWS_REGION_OPTION}"

# print usage information
if [ "$print_help" = "yes" ]; then
  cat <<EOF
  Quickly deploy your new application JAR files to ec2 instances and restart your service.

  usage: 
        quick-deploy --aws-profile=<your-aws-profile-name> --aws-region=cn-northwest-1 <instance name of id> <your local jar file path>

  options:
        --aws-profile=NIKE.SSO.AdminRole  The aws profile name to use, required.
        --aws-region=cn-northwest-1       The aws region to use, optional if region already set with profile or AWS_REGION env variable.
        --help                            Print the help message.
EOF
  exit 0
fi

# aws cli available?
BOLD=$(tput bold)
NORMAL=$(tput sgr0)
if ! which -s aws;  then
  echo "You don't have the required AWS CLI(aws) installed! You may install with: ${BOLD}brew install awscli${NORMAL}"
  exit 3
fi

# jq cli available?
if ! which -s jq; then
 echo "You don't have the required jq installed! You may install with: ${BOLD}brew install jq${NORMAL}"
 exit 3
fi

# aws credentials ok?
if ! ${AWS_CLI_WRAPPER} sts get-caller-identity &>/dev/null; then
  echo "You don't have a valid credential yet, did you run gimme-aws-creds?" && exit 1
fi

# try to resolve instance id from instance name if necessary
if ! [[ "$target" =~ ^i-[0-9]+ ]]; then
  echo "Trying to resolve ec2 instance id from instance name: ${target}..."
  instance_id=$(${AWS_CLI_WRAPPER} ec2 describe-instances --filters "Name=tag:Name, Values=${target}" "Name=instance-state-name, Values=running" --query "Reservations[*].Instances[*].[InstanceId]" --output text)
  if ! [[ "$instance_id" =~ ^i-[0-9]+ ]]; then
    echo "Can't resolve a running instance id from name: ${target}! Are you using the correct instance name?" && exit 2
  fi
  target=$instance_id
  echo "Found running ec2 instance: ${target}!"
fi

# Stop
SSM_CMD_STOP=$(cat <<EOF
${AWS_CLI_WRAPPER} ssm send-command \
--document-name "AWS-RunShellScript" \
--targets '[{"Key":"InstanceIds","Values":["${target}"]}]' \
--parameters '{"commands":["#!/bin/bash", "whoami", "su ssm-user", "sudo systemctl stop springboot.service"]}' | jq -r .Command.CommandId
EOF
)
echo "Waiting for service to stop..."
ssm_cmd_id2=$(bash -c "${SSM_CMD_STOP}")

# upload new JAR file to s3
new_jar_md5=$(md5 -q $jar)                
new_jar_s3_path="s3://nike-commerce-test-app-internal-cn-northwest-1/${new_jar_md5}.jar"
echo "Uploading your new JAR file(${new_jar_md5}) to s3 bucket..."
${AWS_CLI_WRAPPER} s3 cp "${jar}" "${new_jar_s3_path}"

# download new JAR file to target ec2 instance and restart service
SSM_CMD=$(cat <<EOF
${AWS_CLI_WRAPPER} ssm send-command \
--document-name "AWS-RunShellScript" \
--targets '[{"Key":"InstanceIds","Values":["${target}"]}]' \
--parameters '{"commands":["#!/bin/bash", "whoami", "su ssm-user", "whoami", "pwd", "cd ~", "mkdir -p ~/.aws", "printf \"[default]\nregion = cn-northwest-1\ncredential_source = Ec2InstanceMetadata\" > ~/.aws/config", "cat ~/.aws/config", "aws s3 cp ${new_jar_s3_path} ~", "sudo cp ${new_jar_md5}.jar /usr/local/springboot/app.jar", "sudo chown spring:spring /usr/local/springboot/app.jar", "sudo systemctl start springboot.service"]}' | jq -r .Command.CommandId
EOF
)
ssm_cmd_id=$(bash -c "${SSM_CMD}")

# wait for SSM command to finish
echo "Waiting for service to start..."
${AWS_CLI_WRAPPER} ssm wait command-executed --instance-id "${target}" --command-id "${ssm_cmd_id}"

# cleanup JAR files
${AWS_CLI_WRAPPER} s3 rm "${new_jar_s3_path}"

echo "You new JAR file is succcessfully deployed!"